package com.zyk.common;


import com.zyk.filter.FilterRule;
import org.yaml.snakeyaml.Yaml;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Files;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class ConfigParser {

    /**
     * 以config开头
     * config:
     * dns:
     * equal: [xo.com, github.com]
     * suffix: [baidu.com, x.com]
     * bb:
     * equal: [xxx, yy]
     */
    public static Map<String, List<FilterRule>> parseFromYaml(File file) throws IOException {
        if (cantRead(file) || !file.getName().endsWith(".yaml") || !file.getName().endsWith(".yml")) {
            return new HashMap<>();
        }
        return parseFromYaml(Files.newInputStream(file.toPath()));
    }

    public static Map<String, List<FilterRule>> parseFromYaml(InputStream inputStream) {
        Map<String, List<FilterRule>> res = new HashMap<>();
        Yaml yaml = new Yaml();
        FilterRule.Properties filterProperties = yaml.loadAs(inputStream, FilterRule.Properties.class);
        filterProperties.getConfig().forEach((k, v) -> {
            List<FilterRule> allRules = new ArrayList<>();
            addRules(allRules, FilterRule.RuleType.EQUAL, v.getEqual());
            addRules(allRules, FilterRule.RuleType.EQUAL_IC, v.getEqual_ignore_case());
            addRules(allRules, FilterRule.RuleType.PREFIX, v.getPrefix());
            addRules(allRules, FilterRule.RuleType.PREFIX_IC, v.getPrefix_ignore_case());
            addRules(allRules, FilterRule.RuleType.SUFFIX, v.getSuffix());
            addRules(allRules, FilterRule.RuleType.SUFFIX_IC, v.getSuffix_ignore_case());
            addRules(allRules, FilterRule.RuleType.KEYWORD, v.getKeyword());
            addRules(allRules, FilterRule.RuleType.KEYWORD_IC, v.getKeyword_ignore_case());
            addRules(allRules, FilterRule.RuleType.REGEXP, v.getRegexp());
            res.put(k.toLowerCase(), allRules);
        });
        return res;
    }

    private static boolean cantRead(File file) {
        return null == file || !file.exists() || !file.isFile() || !file.canRead();
    }

    private static void addRules(List<FilterRule> allRules, FilterRule.RuleType ruleType, List<String> rules) {
        if (rules != null) {
            for (String rule : rules) {
                allRules.add(new FilterRule(ruleType, rule));
            }
        }
    }
}